package com.wlyuan.gateway;


import com.wlyuan.gateway.config.BlacklistProperties;
import com.wlyuan.gateway.config.RefererProperties;
import com.wlyuan.gateway.config.SecurityProperties;
import com.wlyuan.gateway.resolver.IpKeyResolver;
import com.wlyuan.gateway.resolver.UriKeyResolver;
import lombok.extern.slf4j.Slf4j;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.boot.context.properties.EnableConfigurationProperties;
import org.springframework.cloud.client.discovery.EnableDiscoveryClient;
import org.springframework.cloud.gateway.filter.ratelimit.KeyResolver;
import org.springframework.cloud.gateway.route.RouteLocator;
import org.springframework.cloud.gateway.route.builder.RouteLocatorBuilder;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Primary;
import org.springframework.web.bind.annotation.RequestMapping;
import reactor.core.publisher.Mono;
import reactor.netty.ReactorNetty;

/**
 * 微服务网关
 *
 * @author yuanjie
 */
@Slf4j
@EnableDiscoveryClient
@SpringBootApplication
@EnableConfigurationProperties({SecurityProperties.class, BlacklistProperties.class, RefererProperties.class})
public class GatewayWebApplication {

    public static void main(String[] args) {
        System.setProperty(ReactorNetty.NATIVE, "false");
        System.setProperty(ReactorNetty.IO_WORKER_COUNT, "6");
        System.setProperty(ReactorNetty.IO_SELECT_COUNT, "6");
        SpringApplication.run(GatewayWebApplication.class, args);
    }

    @Bean
    @Primary
    public KeyResolver ipKeyResolver() {
        return new IpKeyResolver();
    }

    @Bean
    public KeyResolver uriKeyResolver() {
        return new UriKeyResolver();
    }

    @Bean
    public RouteLocator myRoutes(RouteLocatorBuilder builder) {
        return builder.routes()
                .route(p -> p
                        .path("/get")
                        .filters(f -> f.addRequestHeader("Hello", "World"))
                        .uri("http://httpbin.org:80"))
                .route(p -> p
                        .host("*.circuitbreaker.com")
                        .filters(f -> f.circuitBreaker(config -> config
                                .setName("mycmd")
                                .setFallbackUri("forward:/fallback")))
                        .uri("http://httpbin.org:80"))
                .build();
    }

    @RequestMapping("/fallback")
    public Mono<String> fallback() {
        return Mono.just("fallback");
    }
}

